import { AxiosRequestConfig, AxiosResponse, } from 'axios'
import type { RequestOptions, Result, ResultType } from '@/types/axios'
import { isString } from "@/utils/is.ts";
import { useGlobSetting } from '@/hooks/setting'

export interface CreateAxiosOptions extends AxiosRequestConfig {
  authenticationScheme?: string
  transform?: AxiosTransform
  requestOptions?: RequestOptions
}

export abstract class AxiosTransform {
  /**
   * @description: 在发送请求之前调用的函数。它可以根据需要修改请求配置
   */
  beforeRequestHook?: (config: AxiosRequestConfig, options: RequestOptions) => AxiosRequestConfig
  /**
   * @description: 处理响应数据
   */
  transformResponseHook?: (res: AxiosResponse<Result>, options: RequestOptions) => any
}

const globSetting = useGlobSetting()
/**
 * @description: 数据处理，方便区分多种处理方式
 */
export const transform: CreateAxiosOptions = {
  authenticationScheme: 'Bearer',
  transform: {
    /**
     * @description: 处理响应数据。如果数据不是预期格式，可直接抛出错误
     */
    transformResponseHook: (res: AxiosResponse<ResultType>, options: RequestOptions) => {
      const { data, status } = res
      if (status >= 200 && status < 300) {
        return data
      } else if (status === 401) {
        console.log(res, data, options, 'axiosTransform')
        throw new Error(`token无效`)
      } else if (status >= 400 && status < 500) {
        //非404报错提示
        throw new Error(`${data}`)
      } else if (status >= 500 && status < 600) {
        throw new Error(`${data}`)
      } else {
        throw new Error(`网络请求错误，状态码${status}`)
      }
    },
    // 请求之前处理config
    beforeRequestHook: (config, options) => {
      const { apiUrl } = options
      if (apiUrl && isString(apiUrl))
        config.url = `${apiUrl}${config.url}`
      return config
    },
  },
  // 配置项，下面的选项都可以在独立的接口请求中覆盖
  requestOptions: {
    // 默认将prefix 添加到url
    joinPrefix: true,
    // 是否返回原生响应头 比如：需要获取响应头时使用该属性
    isReturnNativeResponse: false,
    // 需要对返回数据进行处理
    isTransformResponse: true,
    // post请求的时候添加参数到url
    joinParamsToUrl: false,
    // 格式化提交参数时间
    formatDate: true,
    // 消息提示类型
    errorMessageMode: 'message',
    // 接口地址
    apiUrl: globSetting.apiUrl,
    // 接口拼接地址
    urlPrefix: globSetting.urlPrefix,
    //  是否加入时间戳
    joinTime: true,
    // 忽略重复请求
    ignoreCancelToken: true,
    // 是否携带token
    withToken: true,
    retryRequest: {
      isOpenRetry: true,
      count: 5,
      waitTime: 100,
    },
  },
}
